import 'dart:io';

import 'package:fbroadcast/fbroadcast.dart';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:video_player/video_player.dart';
import 'package:xvideos/hj_model/video_model.dart';
import 'package:xvideos/hj_page/short_video/view/short_video_loading.dart';
import 'package:xvideos/hj_page/short_video/view/short_video_menu.dart';
import 'package:xvideos/hj_utils/global.dart';
import 'package:xvideos/hj_utils/screen.dart';

import 'package:xvideos/tools_base/event_bus/events.dart';

import '../../../alert_business/video/video_buy_bottom_sheet.dart';
import '../../../alert_business/video/vip_dailog.dart';
import '../../../hj_model/splash/watch_count_model.dart';
import '../../../hj_utils/api_service/vid_service.dart';
import '../../../hj_utils/event_tracking_manager.dart';
import '../../../hj_utils/free_play_count_manager.dart';
import '../../../hj_utils/history_record_util.dart';
import '../../../hj_utils/player_util.dart';
import '../../../tools_base/debug_log.dart';
import '../../../tools_base/global_store/store.dart';
import '../../../tools_base/video_download/video_download_manager.dart';

import '../../main_page/main_page_logic.dart';
import '../../pre_sale/pre_sale_provider.dart';
import '../../video/view/detail_top_right_view.dart';
import '../short_video_logic.dart';
import '../short_video_page.dart';

class ShortVideoPlayer extends StatefulWidget {
  const ShortVideoPlayer({
    Key? key,
    this.isCurrentPage,
    required this.index,
    required this.videoInfo,
    this.callback,
    this.isFromCollect = false,
    this.tabIndex,
    this.fctType,
    this.superTabController,
  }) : super(key: key);

  final int index;
  final int? tabIndex;
  final VideoModel? videoInfo;
  final bool? isFromCollect;
  final bool? isCurrentPage;
  final VideoListType? fctType;
  final TabController? superTabController;
  final Function(VideoPlayerController?)? callback;

  @override
  State<ShortVideoPlayer> createState() => _ShortVideoPlayerState();
}

class _ShortVideoPlayerState extends State<ShortVideoPlayer> {
  VideoPlayerController? controller;

  VideoModel? get detailVideoInfo {
    if (widget.fctType == VideoListType.SECOND && widget.videoInfo?.detailVModel != null) {
      return widget.videoInfo?.detailVModel;
    }
    return widget.videoInfo;
  }

  int currentTabIndex = 1;
  VideoResolution? resolutionSize;

  /// 播放的视频是否是竖屏状态
  bool playerIsVertical = true;

  double get containerWidth => screen.screenHeight;

  double get containerHeight => screen.screenWidth;

  double get videoWidth => screen.screenWidth;

  double get videoHeight => (controller?.value.aspectRatio ?? 1) * screen.screenWidth;

  VideoResolution get rotateWH => configVideoSize(containerWidth, containerHeight, videoWidth, videoHeight, true);
  bool showRotatedBox = false;
  bool _isShowAlertIng = false;
  WatchCount? watchCount;
  bool isPlayLocalCacheVideo = false; // 播放缓存视频
  bool isHistoryRecord = false; // 历史记录
  LongVideStatus  get videoStatus => longVideoStatusDesc(detailVideoInfo);
  bool get isCurrentRootMenu { // true:底部根菜单在抖音位置
    return Get.find<MainPageLogic>().state.curIndex == 1;
  }
  @override
  void initState() {
    super.initState();
    _initVideoPlayer(detailVideoInfo);
    _freeCountWatch();
    ShortVideoLogic.addPlayListener(_playVideoLister);
    FBroadcast.instance().register(SWITCH_CDN_ADDRESS, _switchLineRefreshVideo);

    if (widget.fctType == VideoListType.SECOND && widget.videoInfo?.detailVModel == null) {
      // 从列表页进入短视频,需要获取视频详情数据,来处理权限问题;(列表数据服务端为了速度,没有获取相关权限数据,前端单独获取)
      _loadVideoDetail(canRetry: true);
    }
  }

  @override
  void didUpdateWidget(covariant ShortVideoPlayer oldWidget) {
    super.didUpdateWidget(oldWidget);
    if (widget.fctType == VideoListType.RECOMMEND && !isCurrentRootMenu) {
      // 短视频热门保活了,当其他视频全屏切换时,即屏幕变成横屏的时候,会刷新整个app, 这里不处理;
      // 不在当前屏幕没有渲染的情况下,播放器执行pause, 会影响到当前的播放控制器
      return;
    }
    if (widget.superTabController != null && widget.superTabController!.index != widget.tabIndex) {
      return;
    }
    if (widget.isCurrentPage == true) {
      if (oldWidget.isCurrentPage == true) {
        controller?.play();
      } else {
        controller?.seekTo(Duration.zero).then((value) {
          if (widget.isCurrentPage == true) {
            controller?.play();
          }
        });
      }
      debugLog("page====play:${widget.index}");
      if (widget.callback != null) {
        widget.callback!(controller);
      }
    } else {
      controller?.pause();
      debugLog("page====pause:${widget.index}");
    }
  }

  Future _loadVideoDetail({bool canRetry = false}) async {
    try {
      if (widget.videoInfo?.isLoadingDetail == true) {
        return;
      }
      widget.videoInfo?.isLoadingDetail = true;
      VideoModel? videoModel = await VidService.getVideoDetail(detailVideoInfo?.id ?? '');
      if (videoModel != null) {
        widget.videoInfo?.detailVModel = videoModel;
      }
      widget.videoInfo?.isLoadingDetail = false;
    } catch (e) {
      if (canRetry) {
        _loadVideoDetail(canRetry: false);
      } else {
        widget.videoInfo?.isLoadingDetail = false;
      }
      debugLog(e.toString());
    }
  }

  void _switchLineRefreshVideo(context, value) {
    if (!isPlayLocalCacheVideo) {
      _initVideoPlayer(detailVideoInfo, isRefresh: true);
      if (mounted) {
        setState(() {});
      }
    }
  }

  void _playVideoLister(bool isPlay) {
    if (isPlay) {
      if (widget.isCurrentPage == true && widget.tabIndex == ShortVideoLogic.tabMIndex) {
        controller?.play();
      } else {
        controller?.pause();
      }
    } else {
      controller?.pause();
    }
  }

  _initVideoPlayer(VideoModel? videoInfo, {bool isRefresh = false}) async {
    try {
      debugLog("视频url:${videoInfo?.realVideoUrl}");
      if (videoInfo?.localPath?.isNotEmpty != true) {
        dynamic result = await VideoDownloadManager.instance.searchInfo(
          url: videoInfo?.realVideoUrl,
        );
        if (result is Map) {
          Map fileInfoMap = result;
          String? filePath = fileInfoMap["localPath"];
          if (filePath?.isNotEmpty == true) {
            videoInfo?.localPath = filePath;
          }
        }
      }
      VideoPlayerController? preVideoCtr = controller;
      preVideoCtr?.pause();
      int prePosition = preVideoCtr?.value.position.inSeconds ?? 0;
      if (videoInfo?.localPath?.isNotEmpty == true) {
        isPlayLocalCacheVideo = true;
        controller = VideoPlayerController.file(File(videoInfo?.localPath ?? ""));
      } else {
        isPlayLocalCacheVideo = false;
        controller = VideoPlayerController.networkUrl(Uri.parse(videoInfo?.realVideoUrl ?? ""));
      }
      if (mounted) {
        setState(() {});
      }
      //showToast( "短视频切换线路成功地址是 ${videoInfo?.realVideoUrl}");
      await controller?.initialize();
      preVideoCtr?.removeListener(_listener);
      controller?.addListener(_listener);
      showRotatedBox = (controller?.value.aspectRatio ?? 1) > 1.3;
      if (widget.isCurrentPage == true) {
        if (prePosition > 1) {
          await controller?.seekTo(Duration(seconds: prePosition));
        }
        controller?.play();
        debugLog("page====init play:${widget.index}");
        if (widget.callback != null) {
          widget.callback!(controller);
        }
      }
    } catch (e) {
      showToast("视频资源加载失败");
      debugLog("视频初始化失败：$e");
    }
    if (mounted) {
      setState(() {});
    }
  }

  void _freeCountWatch() async {
    FreePlayCountManager().canFreePlay(detailVideoInfo);
    watchCount = FreePlayCountManager().playCount?.copy();
    presaleProvider.consumeVCoinPrivilegeCount(detailVideoInfo);
    watchCount?.coinWatchCount = presaleProvider.coinVideoFreeCount;
  }

  bool get hasPresaleActivity => presaleProvider.isOpen && !presaleProvider.isPayAll();
  void _listener() async {
    if (!mounted) {
      return;
    }
    if (controller == null) {
      return;
    }
    if(!isCurrentRootMenu && widget.fctType == VideoListType.RECOMMEND){
      controller?.pause();
    }
    if (detailVideoInfo?.freeArea == true) {
      return;
    }
    if (FreePlayCountManager().canFreePlay(detailVideoInfo)) {
      return;
    }
    if (isHistoryRecord == false && controller!.value.position.inSeconds > 1) {
      isHistoryRecord = true;
      HistoryRecordUtil.insertHistoryModel<VideoModel>(detailVideoInfo!, HistoryRecordType.short);
    }

    bool needBuyVipBool = videoStatus.isNeedVip;
    bool needBuyVideoBool = videoStatus.isNeedBuy;
    if ((watchCount?.coinWatchCount ?? -1) >= 0) {
      // 金币视频免费观看权益次数
      needBuyVideoBool = false;
    }
    if (needBuyVideoBool) {
      if (controller!.value.position.inSeconds >= (detailVideoInfo?.freeTime ?? 10)) {
        if (controller?.value.isPlaying == true) {
          controller?.pause();
          if (widget.fctType == VideoListType.SECOND) {
            if (widget.videoInfo?.detailVModel == null) {
              showToast("权限校验失败");
              _loadVideoDetail();
              return;
            }
          }

          ///购买视频
          if (!_isShowAlertIng) {
            _isShowAlertIng = true;
            var result = await Get.bottomSheet(VideoBuyBottomSheet(videoM: detailVideoInfo!, presale: hasPresaleActivity));
            _isShowAlertIng = false;
            EventTrackingManager().addVideoDatas(detailVideoInfo?.id, detailVideoInfo?.title);

            ///true表示支付成功
            if (result == true) {
              detailVideoInfo?.vidStatus?.hasPaid = true;
              controller?.play();
              if (mounted) {
                setState(() {});
              }
            }
          }
        }
      }
    } else if (needBuyVipBool) {
      if (controller!.value.position.inSeconds >= (detailVideoInfo?.freeTime ?? 10)) {
        if (controller?.value.isPlaying == true) {
          controller?.pause();

          ///购买视频
          if (!_isShowAlertIng) {
            _isShowAlertIng = true;
            await Get.dialog(VipDialog(presale: hasPresaleActivity));
            _isShowAlertIng = false;
            await globalStore.updateUserInfo();
            EventTrackingManager().addVideoDatas(detailVideoInfo?.id, detailVideoInfo?.title);

            ///true表示支付成功
            if (globalStore.isVIP()) {
              controller?.play();
              if (mounted) {
                setState(() {});
              }
            }
          }
        }
      }
    } else {}
  }

  @override
  Widget build(BuildContext context) {
    return GestureDetector(
      onTap: () {
        if (controller?.value.isPlaying == true) {
          controller?.pause();
        } else {
          controller?.play();
        }
      },
      onLongPressUp: () {
        controller?.setPlaybackSpeed(1.0);
      },
      onLongPressEnd: (value) {
        controller?.setPlaybackSpeed(1.0);
      },
      onLongPressStart: (detail) {
        showToast("长按不动,2X倍速播放");
        controller?.setPlaybackSpeed(2.0);
      },
      child: Scaffold(
        backgroundColor: Colors.transparent,
        body: Stack(
          fit: StackFit.expand,
          alignment: Alignment.center,
          children: [
            if (controller?.value.isInitialized == true) ...[
              RotatedBox(
                quarterTurns: playerIsVertical ? 0 : 1,
                child: Container(
                  width: playerIsVertical ? null : rotateWH.videoWidth,
                  height: playerIsVertical ? null : rotateWH.videoHeight,
                  alignment: playerIsVertical ? Alignment.center : null,
                  child: AspectRatio(
                    aspectRatio: controller!.value.aspectRatio, // ?? resolutionSize?.aspectRatio ?? 1,
                    child: VideoPlayer(controller!),
                  ),
                ),
              ),
            ],
            ShortVideoLoading(controller: controller),
            ShortVideoMenu(
              model: detailVideoInfo,
              controller: controller,
              watchCount: watchCount,
            ),
            _getRotateButton(),
          ],
        ),
      ),
    );
  }

  /// 左边旋转按钮,如果是水平视频
  Widget _getRotateButton() {
    return Visibility(
      visible: false, // showRotatedBox,
      child: Align(
        alignment: Alignment.centerLeft,
        child: Container(
          padding: const EdgeInsets.only(left: 10),
          child: InkWell(
            onTap: () {
              playerIsVertical = !playerIsVertical;
              setState(() {});
            },
            // child: svgAssets(
            //   playerIsVertical ? AssetsSvg.VIDEO_IC_ROTATE_V : AssetsSvg.VIDEO_IC_ROTATE_H,
            //   width: 28,
            //   height: 28,
            // ),
          ),
        ),
      ),
    );
  }

  @override
  void dispose() {
    ShortVideoLogic.removePlayListener(_playVideoLister);
    FBroadcast.instance().remove(_switchLineRefreshVideo, key: SWITCH_CDN_ADDRESS);
    if (controller?.value.isInitialized == true && (controller?.value.position.inSeconds ?? 0) > 0) {
      HistoryRecordUtil.insertHistoryModel<VideoModel>(detailVideoInfo!, HistoryRecordType.short);
    }
    controller?.removeListener(_listener);
    controller?.dispose();
    //  eventBus.off(EventBus.eventTabBarSelectedIndex, _tabMenuExchange);
    debugLog("dispose--> page ${widget.index}");

    try {
      EventTrackingManager.uploadEvent("视频记录", eventProperties: {
        //"跳转路由": widget.linkRoute,
        "视频类型": "短视频",
        "用户身份": globalStore.isVIP() ? "VIP" : "非VIP",
        "标题": detailVideoInfo!.title.toString(),
        "id": detailVideoInfo!.id.toString(),
        //"标签": tagsName.toString(),
        "价格": detailVideoInfo!.coins,
        "是否VIP视频": detailVideoInfo!.coins == 0 ? "是" : "否",
        "播放量": detailVideoInfo!.playCount,
        "点赞量": detailVideoInfo!.likeCount,
        "收藏量": detailVideoInfo!.collectCount,
        "评论量": detailVideoInfo!.commentCount,
        "总时长": "${controller?.value.duration.inSeconds}秒",
        "当前播放时长": "${controller?.value.position.inSeconds}秒",
        "当前播放进度": "${((controller!.value.position.inMilliseconds / controller!.value.duration.inMilliseconds) * 100).toInt()}%",
      });
    } catch (e) {
      debugLog(e);
    }
    super.dispose();
  }
}
